package com.example.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.example.delegator.CustomClassificationNodeDelegator;
import com.example.delegator.CustomEXADefinitionDelegator;
import com.example.dto.CategoryNodeInfoViewDTO;
import com.example.dto.EnumViewDTO;
import com.example.result.ReturnCode;
import com.example.result.ReturnResult;
import com.example.service.IPartService;
import com.example.vo.*;
import com.huawei.innovation.rdm.coresdk.basic.dto.VersionCheckOutDTO;
import com.huawei.innovation.rdm.coresdk.basic.dto.VersionUndoCheckOutDTO;
import com.huawei.innovation.rdm.coresdk.basic.dto.VersionUpdateAndCheckinDTO;
import com.huawei.innovation.rdm.coresdk.basic.dto.MasterIdModifierDTO;
import com.huawei.innovation.rdm.coresdk.basic.enums.ConditionType;
import com.huawei.innovation.rdm.coresdk.basic.vo.QueryCondition;
import com.huawei.innovation.rdm.coresdk.basic.vo.QueryRequestVo;
import com.huawei.innovation.rdm.coresdk.basic.vo.RDMPageVO;
import com.huawei.innovation.rdm.coresdk.extattrmgmt.dto.EXAValueParamDTO;
import com.huawei.innovation.rdm.coresdk.extattrmgmt.dto.EXAValueViewDTO;
import com.huawei.innovation.rdm.lwxminibom.bean.enumerate.AssemblyMode;
import com.huawei.innovation.rdm.lwxminibom.bean.enumerate.PartSource;
import com.huawei.innovation.rdm.lwxminibom.dto.entity.*;
import com.huawei.innovation.rdm.xdm.delegator.ClassificationNodeDelegator;
import com.huawei.innovation.rdm.xdm.dto.entity.ClassificationNodeBusinessCodeDTO;
import com.huawei.innovation.rdm.xdm.dto.entity.ClassificationNodeViewDTO;
import com.huawei.innovation.rdm.lwxminibom.delegator.PartDelegator;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;


@Service
public class PartService implements IPartService {
    private static final Logger logger= LoggerFactory.getLogger(PartService.class);

    @Autowired
    private CustomEXADefinitionDelegator customEXADefinitionDelegator;

    @Autowired
    private CustomClassificationNodeDelegator customClassificationNodeDelegator;

    @Autowired
    private PartDelegator partDelegator;
    @Autowired
    private ClassificationNodeDelegator classificationNodeDelegator;

    @Override
    public ReturnResult createPart(PartCreateFormVO partCreateFormVO) {
        PartCreateDTO partCreateDTO = new PartCreateDTO();

        //前端-创建清单对象 --> 后端-Part创建传输对象
        partCreateDTO.setName(partCreateFormVO.getName());
        partCreateDTO.setPartType(partCreateFormVO.getAssemblyMode());
        partCreateDTO.setSource(partCreateFormVO.getPartSource());
        //设置master对象 branch对象
        PartMasterCreateDTO partMasterCreateDTO = new PartMasterCreateDTO();
        partMasterCreateDTO.setName(partCreateFormVO.getName());
        partCreateDTO.setMaster(partMasterCreateDTO);
        partCreateDTO.setBranch(new PartBranchCreateDTO());
        //设置分类属性
        JSONObject jsonObject = new JSONObject();
        jsonObject.fluentPut("Classification",partCreateFormVO.getClsAttrs());
        JSONArray clsAttrs = new JSONArray();
        clsAttrs.add(jsonObject);

        partCreateDTO.setClsAttrs(clsAttrs);
        //扩展属性
        //通过businessCode查询id
        ClassificationNodeBusinessCodeDTO businessCodeDTO = new ClassificationNodeBusinessCodeDTO();
        businessCodeDTO.setBusinessCode(partCreateFormVO.getNumber());
        ClassificationNodeViewDTO byBusinessCode = classificationNodeDelegator.getByBusinessCode(businessCodeDTO);
        Long id = byBusinessCode.getId();

        List<EXAValueParamDTO> extAttrs = new ArrayList<>();
        EXAValueParamDTO exaValueParamDTO = new EXAValueParamDTO();
        exaValueParamDTO.setName("Classification");
        exaValueParamDTO.setValue(id);
        extAttrs.add(exaValueParamDTO);

        partCreateDTO.setExtAttrs(extAttrs);
        //创建Part
        PartViewDTO partViewDTO = partDelegator.create(partCreateDTO);
        JSONObject r = new JSONObject();
        r.put("id",partViewDTO.getId());
        //返回
        return new ReturnResult(ReturnCode.INSERT_OK,"创建Part成功",r);
    }

    @Override
    public ReturnResult getEnum(String enumType) {
        logger.info("PartService.getEnum "+" 查询枚举值");
        List<EnumViewDTO> queryResult = customEXADefinitionDelegator.queryAllEnumInfo();
        EnumViewDTO r=null;
        for (EnumViewDTO e :
                queryResult) {
            if(e.getName().equals(enumType)){
                r = e;break;
            }
        }
        if(r==null){
            return new ReturnResult(ReturnCode.GET_ERR,"查无此枚举类型",null);
        }
        EnumValuesListVO enumValuesListVO = new EnumValuesListVO();
        enumValuesListVO.setEnumValueList(r.getEnumValueList());
        return  new ReturnResult(ReturnCode.GET_OK,"查询枚举类型："+enumType+" 成功",enumValuesListVO);
    }
    @Override
    public ReturnResult getClassificationChildrenNodeByParams(String parentId, Boolean enable) {
        List<ClassificationNodeViewDTO> list = customClassificationNodeDelegator.getChildren(parentId, enable);
        List<CustomClassificationNodeViewVO> newlist = new ArrayList<>();
        for (ClassificationNodeViewDTO e :
                list) {
            CustomClassificationNodeViewVO customClassificationNodeViewVO = new CustomClassificationNodeViewVO();
            customClassificationNodeViewVO.setId(String.valueOf(e.getId()));
            customClassificationNodeViewVO.setBusinessCode(e.getBusinessCode());
            customClassificationNodeViewVO.setDescription(e.getDescription());
            customClassificationNodeViewVO.setName(e.getName());
            customClassificationNodeViewVO.setNameEn(e.getNameEn());
            newlist.add(customClassificationNodeViewVO);
        }
        return new ReturnResult(ReturnCode.GET_OK,"获取子节点成功",newlist);
    }

    @Override
    public ReturnResult getOneLevelClassificationCatalogue(boolean enable) {
        List<ClassificationNodeViewDTO> list = customClassificationNodeDelegator.getOneLevelClassificationType(enable);
        List<CustomClassificationNodeViewVO> newlist = new ArrayList<>();
        for (ClassificationNodeViewDTO e :
                list) {
            CustomClassificationNodeViewVO customClassificationNodeViewVO = new CustomClassificationNodeViewVO();
            customClassificationNodeViewVO.setId(String.valueOf(e.getId()));
            customClassificationNodeViewVO.setBusinessCode(e.getBusinessCode());
            customClassificationNodeViewVO.setDescription(e.getDescription());
            customClassificationNodeViewVO.setName(e.getName());
            customClassificationNodeViewVO.setNameEn(e.getNameEn());
            newlist.add(customClassificationNodeViewVO);
        }
        return new ReturnResult(ReturnCode.GET_OK,"一级分类获取成功", newlist);
    }

    @Override
    public ReturnResult query(PartQueryParamVO partQueryParamVO) {
        String part_number= partQueryParamVO.getPartNumber();
        String part_name = partQueryParamVO.getPartName();
        logger.info("PartService.query"+"   "+"查询的partNumber:"+part_number);
        logger.info("PartService.query"+"   "+"查询的partName:"+part_name);

        QueryRequestVo queryRequestVo = new QueryRequestVo();
        QueryCondition queryCondition = new QueryCondition();

        if(part_number!=null&&part_name!=null){
            queryCondition.setJoiner("and");
        } else {
            queryCondition.setJoiner("or");
        }
        if(part_number!=null){
            queryCondition.addCondition("master.number",ConditionType.EQUAL, part_number);
        }
        if(part_name!=null){
            queryCondition.addCondition("master.name", ConditionType.EQUAL, part_name);
        }

        queryRequestVo.setFilter(queryCondition);
        List<PartViewDTO> query = partDelegator.find(queryRequestVo, new RDMPageVO());
        if(query == null || query.isEmpty()){
            return new ReturnResult(ReturnCode.GET_ERR, "查询为空", null);
        }

        Map<Long,PartViewDTO> map=new HashMap<>();
        for(PartViewDTO partViewDTO:query){
            Long new_part_id=partViewDTO.getMaster().getId();
            if(!map.containsKey(new_part_id)){
                map.put(new_part_id,partViewDTO);
            }else{
                Integer new_iteration=partViewDTO.getIteration();
                PartViewDTO old_partViewDTO=map.get(new_part_id);
                Integer old_iteration=old_partViewDTO.getIteration();
                if(new_iteration>old_iteration){
                    map.put(new_part_id,partViewDTO);
                }
            }
        }

        List<PartQueryResultVO> result = new ArrayList<>();

        for(PartViewDTO partViewDTO : map.values()) {

            PartQueryResultVO partQueryResultVO =new PartQueryResultVO();
            partQueryResultVO.setPartId(partViewDTO.getMaster().getId().toString());
            partQueryResultVO.setPartName(partViewDTO.getMaster().getName());
            partQueryResultVO.setPartNumber(partViewDTO.getMaster().getNumber());
            partQueryResultVO.setVersionId(partViewDTO.getId().toString());
            partQueryResultVO.setIteration(partViewDTO.getIteration());
            partQueryResultVO.setPartType(partViewDTO.getPartType() == null ? null : partViewDTO.getPartType());
            partQueryResultVO.setVersion(partViewDTO.getVersion());
            partQueryResultVO.setPartSource(partViewDTO.getSource());
            partQueryResultVO.setClsAttrs(partViewDTO.getClsAttrs());

            List<EXAValueViewDTO> extAttrs = partViewDTO.getExtAttrs();
            for(EXAValueViewDTO exaValueViewDTO:extAttrs){
                PartQueryResultVO newPartQueryResultVO = partQueryResultVO.clone();
                Object object=exaValueViewDTO.getValue();
                String jsonString = JSON.toJSONString(object);
                JSONObject jsonObject = JSON.parseObject(jsonString);
                if(jsonObject!=null){
                    newPartQueryResultVO.setBusinessCode(jsonObject.getString("businessCode"));
                }
                result.add(newPartQueryResultVO);
            }
        }
        return new ReturnResult(ReturnCode.GET_OK, "查询成功", result);
    }

    @Override
    public ReturnResult getCategoryNodeInfo(String id) {
        //通过businessCode获取id
        ClassificationNodeBusinessCodeDTO dto = new ClassificationNodeBusinessCodeDTO();
        dto.setBusinessCode(id);
        ClassificationNodeViewDTO byBusinessCode = classificationNodeDelegator.getByBusinessCode(dto);
        //通过id查询分类属性
        List<CategoryNodeInfoViewDTO> categoryNodeInfo = customClassificationNodeDelegator.getCategoryNodeInfo(byBusinessCode.getId());
        CategoryNodeInfoViewDTO c = categoryNodeInfo.get(0);
        List attrs = c.getAttrs();
        return new ReturnResult(ReturnCode.GET_OK,"查询指定分类结点的全部分类属性 成功",attrs);
    }

    @Override
    public ReturnResult checkoutPart(Long masterId) {
        VersionCheckOutDTO versionCheckOutDTO = new VersionCheckOutDTO();
        versionCheckOutDTO.setMasterId(masterId);
        PartViewDTO partViewDTO = partDelegator.checkout(versionCheckOutDTO);
        return new ReturnResult(ReturnCode.BUSINESS_OK,"检出成功",partViewDTO.getId());
    }

    @Override
    public ReturnResult undoCheckout(Long num) {
        VersionUndoCheckOutDTO versionUndoCheckOutDTO = new VersionUndoCheckOutDTO();
        versionUndoCheckOutDTO.setMasterId(num);
        PartViewDTO partViewDTO = partDelegator.undoCheckout(versionUndoCheckOutDTO);
        return new ReturnResult(ReturnCode.BUSINESS_OK,"撤销成功",num);
    }

    @Override
    public ReturnResult updateAndCheckinPart(PartUpdateAndCheckinFormVO vo) {
        //制作更新请求对象
        VersionUpdateAndCheckinDTO<PartUpdateByAdminDTO> dto = new VersionUpdateAndCheckinDTO<>();
        //部件主对象id
        dto.setMasterId(vo.getMasterId());
        //制作data体
        PartUpdateByAdminDTO partUpdateByAdminDTO = new PartUpdateByAdminDTO();

        String modeStr = vo.getAssemblyMode();
        switch (modeStr) {
            case "Separable", "可分离" -> partUpdateByAdminDTO.setPartType(AssemblyMode.Separable);
            case "Inseparable", "不可分离" -> partUpdateByAdminDTO.setPartType(AssemblyMode.Inseparable);
            case "Part", "零件" -> partUpdateByAdminDTO.setPartType(AssemblyMode.Part);
        }

        String partSourceStr = vo.getPartSource();
        switch (partSourceStr) {
            case "Make", "制造" -> partUpdateByAdminDTO.setSource(PartSource.Make);
            case "Buy", "购买" -> partUpdateByAdminDTO.setSource(PartSource.Buy);
            case "Buy_SingleSource", "购买-单一供应源" -> partUpdateByAdminDTO.setSource(PartSource.Buy_SingleSource);
        }

        //分类相关的属性列表
        JSONObject jsonObject = new JSONObject();
        jsonObject.fluentPut("Classification",vo.getClsAttrs());
        JSONArray clsAttrs = new JSONArray();
        clsAttrs.add(jsonObject);
        partUpdateByAdminDTO.setClsAttrs(clsAttrs);
        //扩展属性列表
        List<EXAValueParamDTO> extAttrs = new ArrayList<>();
        EXAValueParamDTO exaValueParamDTO = new EXAValueParamDTO();
        exaValueParamDTO.setName("Classification");
        //通过分类编码 CNxxxx 获取分类id
        String clsNumber = vo.getClsNumber();
        ClassificationNodeBusinessCodeDTO businessCodeDTO = new ClassificationNodeBusinessCodeDTO();
        businessCodeDTO.setBusinessCode(clsNumber);
        ClassificationNodeViewDTO byBusinessCode = classificationNodeDelegator.getByBusinessCode(businessCodeDTO);
        Long clsId = byBusinessCode.getId();
        //设置分类id
        exaValueParamDTO.setValue(clsId);
        extAttrs.add(exaValueParamDTO);
        partUpdateByAdminDTO.setExtAttrs(extAttrs);
        //主对象
        PartMasterUpdateByAdminDTO mdto = new PartMasterUpdateByAdminDTO();
        mdto.setNumber(vo.getNumber());
        mdto.setName(vo.getName());
        partUpdateByAdminDTO.setMaster(mdto);
        //branch对象
        PartBranchUpdateByAdminDTO branch = new PartBranchUpdateByAdminDTO();
        partUpdateByAdminDTO.setBranch(branch);
        //data体制作完成
        dto.setData(partUpdateByAdminDTO);
        //更新并检入
        PartViewDTO partViewDTO = partDelegator.updateAndCheckin(dto);

        return new ReturnResult(ReturnCode.UPDATE_OK,"更新并检入成功",partViewDTO.getId());
    }

    @Override
    public ReturnResult delete(String partId) {
        Long part_id=Long.parseLong(partId);
        logger.info("PartService.delete"+"   "+"删除的partId："+partId);
        MasterIdModifierDTO masterIdModifierDTO=new MasterIdModifierDTO();
        masterIdModifierDTO.setMasterId(part_id);
        int delete = partDelegator.delete(masterIdModifierDTO);
        if(delete==1){
            return new ReturnResult(ReturnCode.DELETE_OK,"删除成功");
        }else{
            return new ReturnResult(ReturnCode.DELETE_ERR,"删除失败");
        }
    }

    @Override
    public List<PartQueryResultVO> queryByVersionId(Long versionId) {
        QueryRequestVo queryRequestVo = new QueryRequestVo();
        QueryCondition queryCondition = new QueryCondition();
        queryCondition.setJoiner("or");

        queryCondition.addCondition("id",ConditionType.EQUAL, versionId);

        queryRequestVo.setFilter(queryCondition);
        List<PartViewDTO> query = partDelegator.find(queryRequestVo, new RDMPageVO());
        if(query==null){
            return null;
        }

        Map<Long,PartViewDTO> map=new HashMap<>();
        for(PartViewDTO partViewDTO:query){
            Long new_part_id=partViewDTO.getMaster().getId();
            if(!map.containsKey(new_part_id)){
                map.put(new_part_id,partViewDTO);
            }else{
                Integer new_iteration=partViewDTO.getIteration();
                PartViewDTO old_partViewDTO=map.get(new_part_id);
                Integer old_iteration=old_partViewDTO.getIteration();
                if(new_iteration>old_iteration){
                    map.put(new_part_id,partViewDTO);
                }
            }
        }

        List<PartQueryResultVO> result = new ArrayList<>();

        for(PartViewDTO partViewDTO : map.values()) {
            PartQueryResultVO partQueryResultVO =new PartQueryResultVO();
            partQueryResultVO.setPartId(partViewDTO.getMaster().getId().toString());
            partQueryResultVO.setPartName(partViewDTO.getMaster().getName());
            partQueryResultVO.setPartNumber(partViewDTO.getMaster().getNumber());
            partQueryResultVO.setVersionId(partViewDTO.getId().toString());
            partQueryResultVO.setIteration(partViewDTO.getIteration());
            partQueryResultVO.setPartType(partViewDTO.getPartType() == null ? null : partViewDTO.getPartType());
            partQueryResultVO.setVersion(partViewDTO.getVersion());
            partQueryResultVO.setPartSource(partViewDTO.getSource());
            partQueryResultVO.setClsAttrs(partViewDTO.getClsAttrs());

            List<EXAValueViewDTO> extAttrs = partViewDTO.getExtAttrs();
            for(EXAValueViewDTO exaValueViewDTO:extAttrs){
                PartQueryResultVO newPartQueryResultVO = partQueryResultVO.clone();

                Object object=exaValueViewDTO.getValue();
                String jsonString = JSON.toJSONString(object);
                JSONObject jsonObject = JSON.parseObject(jsonString);

                if(jsonObject!=null){
                    newPartQueryResultVO.setBusinessCode(jsonObject.getString("businessCode"));
                }
                result.add(newPartQueryResultVO);
            }
        }
        return result;
    }
}
